
#ifndef ESFERAS_H_
#define ESFERAS_H_

#include <list>
#include <cmath>

#include "esfera.h"


/*
 * Definimos a Voxel como un array [4] de float 
 * */
typedef float Voxel[4];
 

/*
 * Representa un cubo lleno de esferas tridimensionales.
 *
 */
class CuboDeEsferas {
   private:
      CuboDeEsferas(const CuboDeEsferas &aCopiar);
      const CuboDeEsferas& operator=(const CuboDeEsferas &aCopiar);

      std::list<Esfera> esferas;

      typedef std::list<Esfera>::iterator It;
      typedef std::list<Esfera>::const_iterator Itconst;

      inline float truncar(float num) const {
         return num > 1.0 ? 1.0 : num;
      }

   public:

      CuboDeEsferas() {}

      inline void agregar(const Esfera &esfera) {
         esferas.push_back(esfera);
      }

      inline void limpiar() {
         esferas.clear();
      }

      void getColorVoxel(float x, float y, float z, Voxel &v) const {
         // aumentar este valor para dar mas opacidad a las esferas
         float densidadMaximaEsfera = 1.0; 

         float densidadTotal = 0;
         float rojo = 0; 
         float verde = 0;
         float azul = 0;

         for(Itconst it = esferas.begin(); it != esferas.end(); ++it) {
            float deltaX = pow(it->x() - x, 2);
            float deltaY = pow(it->y() - y, 2);
            float deltaZ = pow(it->z() - z, 2);

            // distancia del voxel al centro de la esfera
            float distanciaAlCentro = sqrt(deltaX + deltaY + deltaZ);

            if(distanciaAlCentro < it->radio()) { //si está dentro de la esfera

               // varia entre minimo y escalar+minimo
		const float minimo = 0.1;
		const float escalar = 0.5;

               float densidad = (escalar * (distanciaAlCentro / it->radio()) + minimo);

               rojo += it->r() * densidad;
               verde += it->g() * densidad;
               azul += it->b() * densidad; 

               densidadTotal += densidad * densidadMaximaEsfera / esferas.size();
            }
         }

         v[0] = truncar(rojo);
         v[1] = truncar(verde);
         v[2] = truncar(azul);
         v[3] = truncar(densidadTotal);
      }
};

#endif
